/*
 * network.c
 *
 *  Created on: 19 févr. 2013
 *      Author: pierre
 */
//#define _XOPEN_SOURCE >= 500 //voir man gethostname

#include <stdlib.h>
#include <netdb.h>
#include <stdbool.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <sys/types.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
//#include "config.h"
#include <stdbool.h>
#include "network.h"
char hostname;
char data[4096];//Réponse
char *get;
int sent=0;
int tmpres=0;
int htmlstart=0;
char *htmlcontent;
char buf[BUFSIZ+1];
#define couleur(param) printf("\033[%sm",param)
SOCKET sock;
//Sockets
//TODO http://broux.developpez.com/articles/c/sockets/
//HTTP client
//TODO http://coding.debuntu.org/c-linux-socket-programming-tcp-simple-http-client
//Cette structure permet de stocker la config de l'UA
//c'est a dire l'identification du programme
struct nom_du_programme {
	char*version;/*Version du soft*/
	char*system;/*Systeme d'exploitation*/
	char*lang;/*Langue*/
	char*name;/*Nom du soft*/
}nom_du_programme;
//Structure pour l'adresse

struct sockaddr_in_4{
	short sin_family; //famille de protocole pour cette adresse
	unsigned short sin_port; //numéro de port (0=port non utilisé)
	struct in_addr sin_addr; //adresse IP
	char sa_data[14]; // 14 octets d’adresse
	char sin_zero[8]; //non utilisé
}serveur;
struct in_addr_a{
	unsigned long s_addr;//4 octets IPV4
};

struct hostent *addresse;
struct net_errors{

}net_errors;
struct net_errors erreur[256];
void initstruct(void)
{
	for(i=0;i<n;i++)
	{
		//erreur[i]=malloc(sizeof(net_errors));
	}
}
void detruire_struct(void)
{
	//free (erreur);
}
void erreur_reseau(int value)
{

	switch(value)
	{
	case 0:
		printf("Erreur de serveur");
		break;
    case 1:
    	printf("Erreur dns");
    	break;
    default:
    	break;
	}
}
/*Recup le nom et le transforme en IP*/
char *name_resolv(char *ad)
{
		longueur_add_ip=15;
		ip=(char*)malloc(longueur_add_ip+1);
		memset(ip,0,longueur_add_ip+1);
		if((addresse=gethostbyname(ad))==NULL)
		{
			//Name serv n'existe pas
			erreur_reseau(0);
		}
		else if(inet_ntop(AF_INET,ad,ip,longueur_add_ip)==NULL)
		{
			//Erreur DNS
			erreur_reseau(1);
		}
		return ip;//Retourne l'ip du serveur
}

//Création d'une socket
int init_network(void)
{
	int sock;
	  if((sock = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0)
	  {
	    perror("Can't create TCP socket");
	    exit(1);
	  }
	  return sock;

}
char useragent[]="Test";//Ua posionné  à test pour le moment
//Renvoie une chaine de caractères pour l'user agent
char *user_agent_value(char *name,char *version,char *system)
{
	char *nom=nom_du_programme.name;
	char *ver=nom_du_programme.version;
	int lenght_syst_ver=sizeof(name)+sizeof(version);
	char *ver_nom=strncat(nom,ver,lenght_syst_ver);
	char *syst=nom_du_programme.system;
	int lenght_total=sizeof(syst)+lenght_syst_ver;
	return strncat(syst,ver_nom,lenght_total);

}
//Récupére la version du système a partir de la config
void recupere_lua(char *name,char *version,char *os)
{

	nom_du_programme.name=name;
	nom_du_programme.version=version;
	nom_du_programme.system=os;

}
//Construit la requete au serveur
char *requete_au_serveur(char *host, char *page)
{

	char *query;
	char *getpage=page;
	char *http_request="GET /%s HTTP/1.1\r\n User-Agent : %s\r\n\r\n";

	if(getpage[0]=='/')//Si page[pos] est de valeur /
	{
		getpage=getpage+1;//On se déplace de +1 case dans le tab de l'adresse
		printf("Debug: Retire le '/',conversion de %s vers %s\n",page,getpage);
	}
	query=(char *)malloc(strlen(host)+strlen(getpage)+strlen(useragent)+strlen(http_request)-5);
	couleur("33");//Jaune
	printf("Debug: Requete au serveur : %s\n",query);
	printf("Debug: Requete http :%s\n",http_request);
	printf("Debug: Page demandé:%s\n",getpage);
	printf("Debug: UA :%s\n",useragent);
	printf("Debug: hôte:%s\n",host);
	couleur("0");//RAZ
	return query;
}
int tempres(int function)
{
	int restmp=0;
	switch(function)
	{
	case 1:
		restmp=send(sock,get+sent,strlen(get)-sent,0);//Envoi
		break;
	case 2:
		restmp=recv(sock, buf, BUFSIZ, 0);//Réception
		break;
	default:
		restmp=33;
		break;
	}

	return restmp;
}
int sent_and_receive_query(char *host ,char *page)
{
	int ok=0;
	//Envoi d'une requete
	get=requete_au_serveur(host,page);
	printf("Debug : La requete est :%s \n ",get);
	while(sent<strlen(get))
	{
		if(tempres(1)==-1)
		{
			printf("Debug: Impossible d'envoyer la requete");
			ok=33;
		}
		sent =sent+tempres(1);
	}
	//Reception des données
	while(tempres(2)>0)
	{
		if(htmlstart==0)
		{
			htmlcontent=strstr(buf,"\r\n\r\n");
			if(htmlcontent!=NULL)
			{
				htmlstart=1;
				//A changer envoyer vers le parser
				printf(htmlcontent);
				ok=1;
				htmlcontent=htmlcontent+4;
			}
			else
			{
				htmlcontent=buf;
			}
			memset(buf,0,tempres(2));


		}

	}
	if(tmpres<0)
		{
			printf("Erreur lors de la réception de données ");
			ok=0;
		}
	free(get);
	free(ip);

	return ok;

}

